package cn.wp.common.core;

import cn.hutool.core.util.ClassUtil;
import cn.hutool.core.util.StrUtil;
import cn.wp.common.core.web.annotation.RestServiceConfig;
import cn.wp.common.core.web.client.ServiceClientProxyFactoryBean;
import cn.wp.common.core.web.client.ServiceClientProxy;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.support.*;
import org.springframework.context.annotation.Configuration;

import java.util.Set;

/**
 * 动态Bean注册
 */
@Slf4j
@Configuration
public class WpAutoBeanDefinitionRegistryPostProcessor implements BeanDefinitionRegistryPostProcessor {

    /**
     * 实例化时自动执行,通常用反射包获取到需要动态创建的接口类，容器初始化时，此方法执行，创建bean
     * 执行过程与registryBeanWithDymicEdit基本一致
     * @param registry
     * @throws BeansException
     */
    @Override
    public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {
        // 注册Bean定义，容器根据定义返回bean

        // 动态注册serviceProxyBean
        Set<Class<?>> serviceProxySet = ClassUtil.scanPackageByAnnotation(Wp.GlobalPackage, RestServiceConfig.class);
        for (Class<?> clazz : serviceProxySet){
            String beanName = StrUtil.lowerFirst(clazz.getSimpleName());
            Object serviceProxy = ServiceClientProxy.create(clazz);
            BeanDefinitionBuilder beanDefinitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(serviceProxy.getClass());
            GenericBeanDefinition definition =  (GenericBeanDefinition) beanDefinitionBuilder.getRawBeanDefinition();
            // 属性赋值
            definition.getPropertyValues().add("interfaceClass",clazz);
            //definition.getPropertyValues().add("params", params);
            definition.setBeanClass(ServiceClientProxyFactoryBean.class);
            definition.setAutowireMode(GenericBeanDefinition.AUTOWIRE_BY_TYPE);
            // 注册bean定义
            registry.registerBeanDefinition(beanName,definition);
            log.info("Register ServiceProxyBean = " + beanName);
        }

//        //构造bean定义
//        BeanDefinitionBuilder beanDefinitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(AutoBean.class);
//        BeanDefinition beanDefinition = beanDefinitionBuilder.getRawBeanDefinition();
//        //注册bean定义
//        registry.registerBeanDefinition("autoBean", beanDefinition);
//
//
//        // AutoDIBean 的注入方式
//        beanDefinitionBuilder = BeanDefinitionBuilder.genericBeanDefinition(AutoDIBean.class);
//        beanDefinitionBuilder.addConstructorArgValue("自动注入依赖Bean");
//        beanDefinition = beanDefinitionBuilder.getBeanDefinition();
//        registry.registerBeanDefinition("autoDiBean", beanDefinition);
    }


    /**
     * 对象实例化时自动执行
     */
    @Override
    public void postProcessBeanFactory(ConfigurableListableBeanFactory factory) throws BeansException {
        // 注册Bean实例，使用supply接口, 可以创建一个实例，并主动注入一些依赖的Bean；当这个实例对象是通过动态代理这种框架生成时，就比较有用了
//        BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(AutoFacDIBean.class, () -> {
//            AutoFacDIBean autoFacDIBean = new AutoFacDIBean("autoFac");
//            autoFacDIBean.setAutoBean(factory.getBean("autoBean", AutoBean.class));
//            autoFacDIBean.setOriginBean(factory.getBean("originBean", OriginBean.class));
//            return autoFacDIBean;
//        });
//        BeanDefinition beanDefinition = builder.getRawBeanDefinition();
//        ((DefaultListableBeanFactory) factory).registerBeanDefinition("autoFacDIBean", beanDefinition);
    }
}